package com.quartet.modules.file.controller;


import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.quartet.api.ApiResult;
import com.quartet.api.PageResult;
import com.quartet.modules.customer.entity.TCustomerInfo;
import com.quartet.modules.customer.service.TCustomerInfoService;
import com.quartet.modules.file.dto.FileRequestDto;
import com.quartet.modules.file.dto.ToolLocalStorageResponseDto;
import com.quartet.modules.file.entity.ToolLocalStorage;
import com.quartet.modules.file.service.ToolLocalStorageService;
import com.quartet.repository.LocalStorageRepository;
import com.quartet.utils.FileUtil;
import com.quartet.utils.LocaleUtils;
import com.quartet.utils.StringUtils;
import com.quartet.utils.constant.MapServerConstant;
import com.quartet.utils.enums.FileTypeEnum;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.apache.poi.util.IOUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.ObjectUtils;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.time.LocalDateTime;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;

/**
 * 文件管理(TOrder)表控制层
 *
 * @author makejava
 * @since 2021-05-04 16:40:24
 */
@RestController
@RequestMapping("file")
@Slf4j
@Api(tags = "业务：文件管理")
public class FileController {
    @Autowired
    private LocalStorageRepository localStorageRepository;

    @Autowired
    private ToolLocalStorageService toolLocalStorageService;

    @Autowired
    private TCustomerInfoService tCustomerInfoService;

    /**
     * 分页查询所有的文件信息
     *
     * @param fileRequestDto 查询实体
     * @return 所有数据
     */
    @ApiOperation("分页查询所有的文件信息")
    @PostMapping("/selectFilePage")
    public ApiResult<PageResult<ToolLocalStorageResponseDto>> selectFilePage(@RequestBody FileRequestDto fileRequestDto) {
        log.info("---------selectFilePage begin, fileRequestDto is {}----------", fileRequestDto);
        IPage<ToolLocalStorage> page = new Page<>(fileRequestDto.getCurrent(), fileRequestDto.getLimit());
        QueryWrapper<ToolLocalStorage> queryWrapper = new QueryWrapper<>();
        if (!ObjectUtils.isEmpty(fileRequestDto.getCreateStartTime())) {
            queryWrapper.lambda().ge(ToolLocalStorage::getCreateTime, fileRequestDto.getCreateStartTime());
        }
        if (!ObjectUtils.isEmpty(fileRequestDto.getCreateEndTime())) {
            queryWrapper.lambda().le(ToolLocalStorage::getCreateTime, fileRequestDto.getCreateEndTime());
        }

        if (!ObjectUtils.isEmpty(fileRequestDto.getCustomerCode())) {
            queryWrapper.lambda().eq(ToolLocalStorage::getCustomerCode, fileRequestDto.getCustomerCode());
        }
        if (!ObjectUtils.isEmpty(fileRequestDto.getFileType())) {
            queryWrapper.lambda().eq(ToolLocalStorage::getType, fileRequestDto.getFileType());
        }
        queryWrapper.lambda().isNotNull(ToolLocalStorage::getCustomerCode);
        IPage<ToolLocalStorage> dbResult = toolLocalStorageService.page(page, queryWrapper);
        PageResult<ToolLocalStorageResponseDto> pageResult = new PageResult();
        List<ToolLocalStorageResponseDto> toolLocalStorageResponseDtoList = dbResult.getRecords().stream().map(toolLocalStorage -> {
            ToolLocalStorageResponseDto toolLocalStorageResponseDto = BeanUtil.copyProperties(toolLocalStorage, ToolLocalStorageResponseDto.class);
            QueryWrapper<TCustomerInfo> queryWrapper1 = new QueryWrapper<>();
            queryWrapper1.lambda().eq(TCustomerInfo::getCustomerCode, toolLocalStorage.getCustomerCode());
            TCustomerInfo tCustomerInfo = tCustomerInfoService.getOne(queryWrapper1);
            if (!ObjectUtils.isEmpty(tCustomerInfo)) {
                toolLocalStorageResponseDto.setCustomerName(tCustomerInfo.getCustomerName());
            }
            if (LocaleUtils.getLocale().startsWith(MapServerConstant.EN)) {
                toolLocalStorageResponseDto.setType(FileTypeEnum.find(toolLocalStorageResponseDto.getType()).getDescriptionEn());
            } else {
                toolLocalStorageResponseDto.setType(FileTypeEnum.find(toolLocalStorageResponseDto.getType()).getDescription());
            }
            return toolLocalStorageResponseDto;
        }).collect(Collectors.toList());
        pageResult.setTotal(dbResult.getTotal());
        pageResult.setData(toolLocalStorageResponseDtoList);
        log.info("---------selectOrderPage end, data is {}----------", pageResult);
        return ApiResult.ok(pageResult);
    }


    /**
     * 上传客户文件/图片/视频
     *
     * @param customerCode 查询实体
     * @return 所有数据
     */
    @ApiOperation("上传客户文件/图片/视频")
    @PostMapping("/uploadFile")
    public ApiResult uploadFile(@RequestParam("customerCode") String customerCode,
                                @RequestParam("remarks") String remarks,
                                @RequestParam(value = "storageId", required = false) Long storageId,
                                @RequestParam(value = "name") String name,
                                @RequestParam("file") MultipartFile file) {
        log.info("---------uploadFile begin, customerCode and is {},{}----------", customerCode, storageId);
        if (Objects.nonNull(storageId)) {
            //修改文件
            ToolLocalStorage toolLocalStorage = toolLocalStorageService.getById(storageId);
            String path = toolLocalStorage.getPath();
            File file1 = new File(path);
            if (file1.exists()) {
                file1.delete();
            }
        }
        //得到上传时的文件名
        String filename = file.getOriginalFilename();
        //保存到项目指定目录
        String uploadDir = "/opt/file";
//        String uploadDir = "E:\\file";
        //如果目录不存在，自动创建文件夹
        File dir = new File(uploadDir + File.separator + customerCode);
//        File dir = new File(uploadDir);
        if (!dir.exists()) {
            dir.mkdirs();
        }
        //保存文件对象 加上uuid是为了防止文件重名
        File serverFile = new File(uploadDir + File.separator + customerCode + File.separator + filename);
        try {
            file.transferTo(serverFile);
        } catch (IOException e) {
            e.printStackTrace();
        }
        String suffix = FileUtil.getExtensionName(file.getOriginalFilename());
        String type = FileUtil.getFileType(suffix);
        String fileName = "";
        try {
            fileName = StringUtils.isBlank(fileName) ? FileUtil.getFileNameNoEx(file.getOriginalFilename()) : fileName;
            ToolLocalStorage localStorage = new ToolLocalStorage(
                    serverFile.getName(),
                    name,
                    suffix,
                    serverFile.getPath(),
                    type,
                    FileUtil.getSize(file.getSize()),
                    customerCode,
                    remarks
            );
            localStorage.setStorageId(storageId);
            localStorage.setCreateBy("System");
            localStorage.setUpdateBy("System");
            localStorage.setCreateTime(LocalDateTime.now());
            localStorage.setUpdateTime(LocalDateTime.now());
            toolLocalStorageService.saveOrUpdate(localStorage);
        } catch (Exception e) {
            FileUtil.del(serverFile);
            throw e;
        }
        return ApiResult.ok();
    }

    /**
     * 下载客户文件/图片/视频
     *
     * @return 所有数据
     */
    @ApiOperation("下载客户文件/图片/视频")
    @PostMapping("/downloadFile")
    public ApiResult downloadFile(HttpServletRequest request, HttpServletResponse response, @RequestParam("storageId") String storageId)
            throws IOException {
        QueryWrapper<ToolLocalStorage> queryWrapper = new QueryWrapper<>();
        queryWrapper.lambda().eq(ToolLocalStorage::getStorageId, storageId);
        ToolLocalStorage toolLocalStorage = toolLocalStorageService.getOne(queryWrapper);
        //1.获取要下载的文件的绝对路径
        String realPath = toolLocalStorage.getPath();
        //2.获取要下载的文件名
        String fileName = realPath.substring(realPath.lastIndexOf(File.separator) + 1);

        String agent = request.getHeader("User-Agent").toUpperCase(); //获得浏览器信息并转换为大写
        byte[] bytes = agent.contains("MSIE") ? fileName.getBytes() : fileName.getBytes("UTF-8");
        // 各浏览器基本都支持ISO编码
        fileName = new String(bytes, "utf-8");
        // 文件名外的双引号处理firefox的空格截断问题
        response.setHeader("Content-disposition", String.format("attachment; filename=\"%s\"", fileName));

//        response.reset();
//        response.setCharacterEncoding("UTF-8");
//        response.setContentType("application/octet-stream");
//        //3.设置content-disposition响应头控制浏览器以下载的形式打开文件
//        response.addHeader("Content-Disposition","attachment;filename=" + new String(fileName.getBytes(),"utf-8"));
        //获取文件输入流
        InputStream in = new FileInputStream(realPath);
//        int len = 0;
//        byte[] buffer = new byte[1024];
        OutputStream out = response.getOutputStream();
//        while ((len = in.read(buffer)) > 0) {
//            //将缓冲区的数据输出到客户端浏览器
//            out.write(buffer,0,len);
//        }
        IOUtils.copy(in, out);
        out.close();
        in.close();
        return ApiResult.ok();
    }


    /**
     * 根据主键id查询文件详情
     *
     * @param storageId 查询条件
     * @return 所有数据
     */
    @ApiOperation("根据主键id查询文件详情")
    @PostMapping("/queryFileByStorageId")
    public ApiResult<ToolLocalStorageResponseDto> queryFileByStorageId(@RequestParam("storageId") String storageId) {
        ToolLocalStorage toolLocalStorage = toolLocalStorageService.getById(storageId);
        ToolLocalStorageResponseDto toolLocalStorageResponseDto = BeanUtil.copyProperties(toolLocalStorage, ToolLocalStorageResponseDto.class);
        QueryWrapper<TCustomerInfo> queryWrapper1 = new QueryWrapper<>();
        queryWrapper1.lambda().eq(TCustomerInfo::getCustomerCode, toolLocalStorage.getCustomerCode());
        TCustomerInfo tCustomerInfo = tCustomerInfoService.getOne(queryWrapper1);
        if (!ObjectUtils.isEmpty(tCustomerInfo)) {
            toolLocalStorageResponseDto.setCustomerName(tCustomerInfo.getCustomerName());
        }
        log.info("---------queryFileByStorageId begin, toolLocalStorageResponseDto is {}----------", toolLocalStorageResponseDto);
        return ApiResult.ok(toolLocalStorageResponseDto);
    }
}
